1. Field
The present invention relates to computing devices. In particular, but not by way of limitation, the present invention relates to compiling or interpreting scripting code.
2. Background
More and more websites are utilizing source code constructs that are written in high level programming languages that must be compiled or interpreted before many other activities (e.g., layout calculations, rendering) associated with the constructs can be executed. By way of example, ECMAscript-based scripting languages (e.g., JavaScript or Flash) are frequently used in connection with the content that they host. More specifically, JavaScript-based content is ubiquitous, and JavaScripts are run by a JavaScript engine that may be realized by a variety of technologies including interpretation-type engines, HotSpot just-in-time (JIT) compilation (e.g., trace based or function based), and traditional-function-based JIT compilation where native code is generated for the entire body of all the functions that get executed.
Compilation and interpretation of source code constructs, however, is often a processor-intensive process that may adversely affect a user's experience (due to the time it takes to compile or interpret the source code). The HotSpot JITs employ two known approaches to reduce the time it takes to process source code constructs and improve a user's experience: (i) the less frequently executed code is interpreted, and the most frequently executed code is compiled to native code; or (ii) a lightweight and less optimized compilation is carried out for less frequently executed code, and a heavy and optimized compilation is carried out for the most frequently executed code.
Interpretation directly involves running code over a software layer, called an interpreter, which handles the execution of the code by mapping operations to native code functions implemented in native processor ISA and that runs on processor hardware. Because pure interpretation is slow, most of the current JavaScript engines (e.g., JSC/Nitro, V8, Tracemonkey, and the IE9 JavaScript engine) used in browsers are using one form of the JIT technology or the other.
JIT-based engines compile the scripts at runtime to native code, and then the native code is executed on the processor hardware. As a consequence, a browser that uses a JIT-based JavaScript engine compiles and executes each piece of script code as soon as the code is found while parsing the HTML file. And in general, evaluation of scripts forms a large part of browser's overall page load time. For example, if networking delays are not considered, 30% of the page load time may be due to the evaluation of JavaScripts. For a traditional function based JIT JavaScript engine, one-third of the evaluation time for a JavaScript may be due to compilation and the remainder due to execution of the compiled code.
Performance of existing JIT compilers for JavaScript and other dynamically typed languages is still much lower than the compilers for statically typed languages because of the extensive type checking and object layout validation checks that need to be performed. Moreover, languages in addition to dynamically typed scripting languages may have other runtime condition checks built into the high level constructs that slow execution. For example, automatic array-bounds checks and null-pointer checks for the statically typed language Java are processing activities that slow the execution of Java-based constructs.
Although current compilers use type specialization and inline caching, there are many instances where accurate type inference cannot be done; thus these techniques are not always able to improve performance suitably, and even when these techniques are performed, additional improvements in performance are still desirable, particularly for multi-issue superscalar RISC processors, VLIW processors, and processors with SIMD and supporting vectorization.